package models

import (
	"context"
	"go.mongodb.org/mongo-driver/bson"
	"go.mongodb.org/mongo-driver/mongo/options"
	"log"
	"strconv"
)

type UserRoom struct {
	Account   string `bson:"account" json:"account"`
	UserId    string `bson:"user_id" json:"user_id"`
	RoomId    string `bson:"room_id" json:"room_id"`
	Type      int    `bson:"type" json:"type"` // 房间类型 1-独聊房间, 2-群聊房间
	OwnerId   string `bson:"owner_id" json:"owner_id"`
	RoomIcon  string `bson:"room_icon" json:"room_icon"`
	UserIcon  string `bson:"user_icon" json:"user_icon"`
	CreatedAt int64  `bson:"created_at" json:"created_at"`
	UpdatedAt int64  `bson:"updated_at"  json:"updated_at"`
	Desc      string `bson:"desc"  json:"desc"`
	Status    string `bson:"status"  json:"status"`
}

func (UserRoom) CollectionName() string {
	return "user_room"
}

func GetUserRoomByUserIdRoomId(UserId, RoomId string) (*UserRoom, error) {
	ur := &UserRoom{}
	err := MongoDB.Collection(UserRoom{}.CollectionName()).
		FindOne(context.Background(), bson.D{
			{"user_id", UserId},
			{"room_id", RoomId},
		}).Decode(ur)
	return ur, err
}

func GetUserRoomByRoomId(roomId string, userId string) ([]*UserRoom, error) {
	reponseFields := bson.D{{"user_id", 1}} // 只返回"name"和"age"字段
	doc := bson.D{}
	doc = append(doc, bson.E{Key: "room_id", Value: roomId})
	cursor, err := MongoDB.Collection(UserRoom{}.CollectionName()).
		Find(context.Background(), doc, options.Find().SetProjection(reponseFields))
	if err != nil {
		return nil, err
	}
	urs := make([]*UserRoom, 0)
	for cursor.Next(context.Background()) {
		ur := &UserRoom{}
		err := cursor.Decode(ur)
		if ur.UserId == userId {
			continue
		}
		if err != nil {
			return nil, err
		}
		urs = append(urs, ur)
	}
	return urs, nil
}

func JudgeUserIsFriend(u1, u2 string) bool {
	cursor, err := MongoDB.Collection(UserRoom{}.CollectionName()).
		Find(context.Background(), bson.D{
			{"user_id", u1},
			{"type", 1},
		})
	RoomId := make([]string, 0)
	if err != nil {
		log.Printf("[DB ERROR: %V\n", err)
		return false
	}
	for cursor.Next(context.Background()) {
		ur := &UserRoom{}
		err := cursor.Decode(ur)
		if err != nil {
			return false
		}
		RoomId = append(RoomId, ur.RoomId)
	}
	// 获取关联u2单聊房间个数
	cnt, err := MongoDB.Collection(UserRoom{}.CollectionName()).
		CountDocuments(context.Background(), bson.D{
			{"user_id", u2},
			{"type", 1},
			{"room_id", bson.M{"$in": RoomId}},
		})
	if err != nil {
		log.Printf("[DB ERROR : %v]\n", err)
		return false
	}
	if cnt > 0 {
		return true
	}
	return false
}

func FindUserListByRoomID(roomId string, prefixAccount string) ([]*UserRoom, error) {
	reponseFields := bson.D{
		{"user_id", 1},
		{"account", 1},
		{"user_icon", 1},
	}

	doc := bson.D{} // 创建一个空的bson.
	doc = append(doc, bson.E{Key: "room_id", Value: roomId})
	doc = append(doc, bson.E{Key: "type", Value: 1})
	if prefixAccount != "" {
		doc = append(doc, bson.E{"account", bson.D{{"$regex", prefixAccount}}})
	}
	cursor, err := MongoDB.Collection(UserRoom{}.CollectionName()).
		Find(context.Background(), doc, options.Find().SetProjection(reponseFields))
	if err != nil {
		return nil, err
	}
	urs := make([]*UserRoom, 0)
	for cursor.Next(context.Background()) {
		ur := &UserRoom{}
		err := cursor.Decode(ur)
		if err != nil {
			return nil, err
		}

		urs = append(urs, ur)
	}
	return urs, nil
}
func FindFriendsList(userid string) ([]*UserRoom, error) {
	cursor, err := MongoDB.Collection(UserRoom{}.CollectionName()).
		Find(context.Background(), bson.D{
			{"user_id", userid},
			{"type", 2},
		})
	if err != nil {
		return nil, err
	}
	urs := make([]*UserRoom, 0)
	for cursor.Next(context.Background()) {
		ur := &UserRoom{}
		err := cursor.Decode(ur)
		if err != nil {
			return nil, err
		}
		urs = append(urs, ur)
	}
	return urs, nil
}

func GetUserRoomId(u1, u2 string) string {
	cursor, err := MongoDB.Collection(UserRoom{}.CollectionName()).
		Find(context.Background(), bson.D{
			{"user_id", u1},
			{"type", 1},
		})
	RoomId := make([]string, 0)
	if err != nil {
		log.Printf("[DB ERROR: %V\n", err)
		return ""
	}
	for cursor.Next(context.Background()) {
		ur := &UserRoom{}
		err := cursor.Decode(ur)
		if err != nil {
			return ""
		}
		RoomId = append(RoomId, ur.RoomId)
	}
	// 获取关联u2单聊房间个数
	ur2 := &UserRoom{}
	err = MongoDB.Collection(UserRoom{}.CollectionName()).
		FindOne(context.Background(), bson.D{
			{"user_id", u2},
			{"type", 1},
			{"room_id", bson.M{"$in": RoomId}},
		}).Decode(ur2)
	if err != nil {
		log.Printf("[DB ERROR : %v]\n", err)
		return ""
	}
	return ur2.RoomId
}

func InsertOneUserRoom(ur *UserRoom) error {
	_, err := MongoDB.Collection(UserRoom{}.CollectionName()).
		InsertOne(context.Background(), ur)
	return err
}

func DeleteUserRoom(RoomId string) error {
	_, err := MongoDB.Collection(UserRoom{}.CollectionName()).
		DeleteOne(context.Background(), bson.M{
			"room_id": RoomId,
		})
	if err != nil {
		return nil
	}
	return nil
}

// 批量插入测试数据
func InsertManyUserRoom(RoomId string) {
	cursor, _ := MongoDB.Collection(UserBasic{}.CollectionName()).
		Find(context.Background(), bson.D{})
	for cursor.Next(context.Background()) {
		ub := &UserBasic{}
		cursor.Decode(ub)
		var ur UserRoom
		ur.UserId = ub.UserId
		ur.RoomId = RoomId
		ur.Type = 2
		MongoDB.Collection(UserRoom{}.CollectionName()).
			InsertOne(context.Background(), ur)
	}

}

func InsertUserRoomManyDemo(RoomId int, size int) {

	cursor, _ := MongoDB.Collection(UserBasic{}.CollectionName()).
		Find(context.Background(), bson.D{})
	userRoomArray := make([]interface{}, size)
	var i int = 0
	for cursor.Next(context.Background()) {
		ub := &UserBasic{}
		cursor.Decode(ub)
		var ur UserRoom
		ur.UserId = ub.UserId
		ur.RoomId = strconv.Itoa(RoomId + i/100000)
		ur.Account = ub.Account

		ur.UserIcon = "/image/d20ab0d5a4a4a2a466d34f8526916b06.jpeg"
		ur.Type = 1
		userRoomArray[i] = ur
		i = i + 1
	}
	collection := MongoDB.Collection(UserRoom{}.CollectionName())
	_, err := collection.InsertMany(context.TODO(), userRoomArray)
	if err != nil {
		log.Fatal(err)
	}
}
